local Tile = @@src(tile)
local BaseState = require(@@GEN(states,base_state))
local Unit = @@src(unit)

local Area = Class {
   init = function (self, x, y, w, h, r, g, b)
      self.x, self.y, self.w, self.h = x, y, w, h
      self.r, self.g, self.b = r or .3, g or .3, b or .7
   end,
   
   draw = function (self)
      $LG.setColor(self.r, self.g, self.b)
      $LG.rectangle("line", self.x, self.y, self.w, self.h)
      $LG.setColor(1, 1, 1)
   end,
}

return Class{
   __includes = BaseState,
   init = function (self)
      BaseState.init(self)
   end,

   load = function (self)
      self.unit_selection = nil
      self.canvas = $LG.newCanvas()
      self.canvas:renderTo(function ()
	    @@EACH({self.placing_area, self.enemy_area}, v:draw())
      end)
      local deck = Game.player.deck
      local deck_list = deck:list_names()
      @@EACH(deck_list,
	     local _u = Unit(v)
	     v = string.format("%s(%d)", v, _u.cost))
      if not self.deck_view then
	 self.deck_view = self.gui:ul(0, 0, 30*#deck_list+#deck_list, 120, unpack(deck_list))
	 self.deck_view.onclick = function (i, b)
	    self.unit_selection = deck_list[i]
	 end
      end

      if not self.play_button then
	 local x, y = self.gui:bottom_right(120, 30)
	 self.play_button = self.gui:button(x, y, "Play",
					    function (i, b)
					       Game.cursor:clear_selection()
					       Game:switch_state("play")
	 end)
      end
   end,

   menu_toggle = function (self)
      if self.ul or self.ulc then
	 lume.remove(self.gui.elements, self.ul)
	 self.ul = nil
	 return
      end
      self.ul = self.gui:ul(300, 200, 400, 33, "Menu")
      self.ul.onclick = function (i, b)
	 Game:switch_state("mainmenu")
	 lume.remove(self.gui.elements, self.ul)
	 self.ul = nil
      end
   end,

   center = function (self)
      local x, y = Game.cursor:get_position()
      Game.current_screen:center_view(x, y)
      lume.remove(self.gui.elements, self.ulc)
      self.ulc = nil
   end,

   _get_context_menu_items = function (self, x, y)
      if not Game.upool:unit_at(x, y) then
	 return { "Center" }, {{ 1, function () self:center() end }}
      else
	 return {"Remove"}, {{ 1, function ()
				  local _u = Game.upool:unit_at(x, y)
				  _u:destroy()
				  @@INC(Game.player.points, _u.cost)
				  self:remove_menus()
	 end
			    }}
      end
   end,

   context_menu = function (self, x, y, sx, sy)
      @@COND(self.ulc or self.ul: return)
      local items, funcs = self:_get_context_menu_items(x, y)
      self.ulc = self.gui:ul(sx, sy, 400, 33, unpack(items))
      self.ulc.onclick = function (i, b)
	 _match(i, {
		   unpack(funcs),
	 })
      end
   end,
   
   resize = function (self, w, h)
      local w, h = Game.current_map:get_dimensions()
      Game.current_screen:center(w, h)
   end,

   remove_menus = function (self)
      @@WHEN(self.ul:
	     lume.remove(self.gui.elements, self.ul)
	     self.ul = nil,
	     
	     self.ulc:
	     lume.remove(self.gui.elements, self.ulc)
	     self.ulc = nil)
   end,
   
   select = function (self)
      self:remove_menus()
      local area = self.placing_area
      if Game.cursor:is_in_rect (area.x, area.y, area.w, area.h) then
	 local x, y = Game.cursor:get_position ()
	 if Tile(x, y):select() and self.unit_selection then
	    if not Game.upool:unit_at(x, y) then
	       local _u =  Unit(self.unit_selection, x, y)
	       if tonumber(_u.cost) > tonumber(Game.player.points) then return end
	       _u:spawn():activate()
	       @@INC(Game.player.points, -_u.cost)
	    end
	 end
      end
   end,
   
   placing_area = Area(0, 0, 512, 128),
   
   enemy_area = Area(0, 384, 512, 128, .8, .3, .3),

   draw = function (self)
      Game.current_screen:draw({
	    Game.current_map, self.canvas, Game.cursor.grid, Game.cursor, Game.upool})
      self.gui:draw()
      @@CL_RESET()
      $LG.print(Game.player.points, self.deck_view.width + 10, 0)
   end,
}
